﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using HA.ModFlow.Domain.DomainLayer;
namespace HA.Data
{
    [Serializable]
    public class BCSpecifiedHead : BCMT3DMS, ICloneable
    {

        public BCSpecifiedHead(List<string> names)
            : base()
        {


            //this._multiStage = new List<double>();


            //this._multiStageStart = new List<double>();


            //this._multiStageEnd = new List<double>();
            

            //for (int i = 0; i < this.NPeriods; i++)
            //{
            //    this._multiStage.Add(0);
            //    this._multiStageEnd.Add(0);
            //    this._multiStageStart.Add(0);
            //}




            //mt3dms的初始化

            foreach (string name in names)
            {

                MultiValue mv = new MultiValue(name);

                this._specConc.Add(mv);


            }




        }


        public object Clone()
        {
            BCSpecifiedHead bcsh = (BCSpecifiedHead)this.MemberwiseClone();

            bcsh._multiStage = (BCDateDataCollection)this._multiStage.Clone();

            bcsh._multiStageEnd = (BCDateDataCollection)this._multiStageEnd.Clone();

            bcsh._multiStageStart = (BCDateDataCollection)this._multiStageStart.Clone();





            //加入mt3dms部分


            return bcsh;
        }


        //double _stage;

        public double Stage
        {
            get { return this._multiStage.IsDataConst ? _multiStage.ConstData : this._multiStage.BCDatas[0].Value; }
            set
            {
                if (this._multiStage.IsDataConst)
                    this._multiStage.ConstData = value;
                else
                    this._multiStage.BCDatas[0].Value = value;
            }
        }


        BCDateDataCollection _multiStage = new BCDateDataCollection();

        public BCDateDataCollection MultiStage
        {
            get { return _multiStage; }
            set { _multiStage = value; }
        }


        //double _stageStart;

        public double StageStart
        {
            get { return this._multiStageStart.IsDataConst ? _multiStageStart.ConstData : this._multiStageStart.BCDatas[0].Value; }
            set
            {
                if (this._multiStageStart.IsDataConst)
                    this._multiStageStart.ConstData = value;
                else
                    this._multiStageStart.BCDatas[0].Value = value;
            }
        }


        BCDateDataCollection _multiStageStart = new BCDateDataCollection();

        public BCDateDataCollection MultiStageStart
        {
            get { return _multiStageStart; }
            set { _multiStageStart = value; }
        }



        //double _stageEnd;

        public double StageEnd
        {
            get { return this._multiStageEnd.IsDataConst ? _multiStageEnd.ConstData : this._multiStageEnd.BCDatas[0].Value; }
            set
            {
                if (this._multiStageEnd.IsDataConst)
                    this._multiStageEnd.ConstData = value;
                else
                    this._multiStageEnd.BCDatas[0].Value = value;
            }
        }

        BCDateDataCollection _multiStageEnd = new BCDateDataCollection();

        public BCDateDataCollection MultiStageEnd
        {
            get { return _multiStageEnd; }
            set { _multiStageEnd = value; }
        }

        //public override void OnNPeriodsChanged()
        //{
        //    base.OnNPeriodsChanged();

        //    //取得之前数据的个数
        //    int n = this.MultiStage.Count;



        //    //开始更新数据


        //    if (n < this.NPeriods)
        //    {
        //        int nSub = this.NPeriods - n;

        //        for (int i = 0; i < nSub; i++)
        //        {
        //            this.MultiStage.Add(0);
        //            this.MultiStageEnd.Add(0);
        //            this.MultiStageStart.Add(0);
        //        }
        //    }

        //    else
        //    {
        //        int nSub = n - this.NPeriods;
        //        this.MultiStage.RemoveRange(this.NPeriods, nSub);
        //        this.MultiStageEnd.RemoveRange(this.NPeriods, nSub);
        //        this.MultiStageStart.RemoveRange(this.NPeriods, nSub);
        //    }


           

        //    //mt3dms设置

        //    foreach (MultiValue item in this._specConc)
        //    {
        //        item.NPeriods = this.NPeriods;

        //    }








        //}


        public override void MapToModflow(List<double> stressPeriods, List<ValueResult> ijkList, ModFlow.Domain.DomainLayer.ModFlowData mf, FeatureObject owner)
        {
            if (ijkList.Count <= 0) return;
            int k = ijkList[0].K;

            List<int> indice = new List<int>();

            List<SpecifiedHead> SpecifiedHeads = new List<SpecifiedHead>();


            double TotalValue = owner.GetTotalLValue();
            //double currentLength = 0;

            foreach (ValueResult item in ijkList)
            {
                //if (item.K != k)
                //{
                //    k = item.K;
                //    currentLength = 0;
                //}
                indice.Add(mf.GridData.GetIndex(item.I, item.J, item.K));

                SpecifiedHead Specified = new SpecifiedHead(item.I, item.J, item.K, mf.GridData.RowsCount, mf.GridData.ColsCount, mf.GridData.LayersCount, mf.StressPeriods.InnerList.Count);

                if (owner is PointFO)
                {
                    this.assistMapToModFlow(stressPeriods, Specified.EHead, _multiStage);
                    this.assistMapToModFlow(stressPeriods, Specified.SHead, _multiStage);

                    //for (int i = 0; i < this.NPeriods; i++)
                    //{
                    //    Specified.EHead[i] = this._multiStage[i];
                    //    Specified.SHead[i] = this._multiStage[i];
                    //}
                }

                if (owner is LineFO)
                {
                    List<double> starts = new List<double>(stressPeriods.Count);
                    List<double> ends = new List<double>(stressPeriods.Count);

                    foreach (var sp in stressPeriods)
                    {
                        starts.Add(0);
                        ends.Add(0);
                    }

                    this.assistMapToModFlow(stressPeriods, Specified.EHead, _multiStage);
                    this.assistMapToModFlow(stressPeriods, Specified.SHead, _multiStage);
                    this.assistMapToModFlow(stressPeriods, starts, _multiStageStart);
                    this.assistMapToModFlow(stressPeriods, ends, _multiStageEnd);

                    for (int i = 0; i < stressPeriods.Count; i++)
                    {
                        Specified.EHead[i] = starts[i] + (ends[i] - starts[i]) * (item.LineCurrentTotalLength / TotalValue);
                        Specified.SHead[i] = starts[i] + (ends[i] - starts[i]) * (item.LineCurrentTotalLength / TotalValue);

                    }
                    //currentLength += item.Value;

                }


                if (owner is PolygonFO)
                {
                    this.assistMapToModFlow(stressPeriods, Specified.EHead, _multiStage);
                    this.assistMapToModFlow(stressPeriods, Specified.SHead, _multiStage);

                    //river.FirstConductance = this._conductance * item.Value;
                    //for (int i = 0; i < this.NPeriods; i++)
                    //{
                    //    Specified.EHead[i] = this._multiStage[i];
                    //    Specified.SHead[i] = this._multiStage[i];
                    //}
                }
                SpecifiedHeads.Add(Specified);
            }
            //mf.SourceSinks.SpecifiedHeads.UpdateSpecifiedHeads(SpecifiedHeads, indice);
            mf.SourceSinks.SpecifiedHeads.AddTempSpecifiedHeads(SpecifiedHeads);
        }





        //mt3dms 相关的数据

        List<MultiValue> _specConc = new List<MultiValue>();

        public List<MultiValue> SpecConc
        {
            get { return _specConc; }

        }

        public override void MapToMT3DMs(List<double> stressPeriods, MT3DMS.DomainLayer.MT3DMSData data, CoverageSetup setup, FeatureObject fo)
        {
            throw new NotImplementedException();
        }

        public override void OnSpeListChanged(List<string> lst)
        {

            base.OnSpeListChanged(lst);

            //写一个算法，要保证顺序性
            this._specConc.Clear();
            foreach (string name in lst)
            {

                MultiValue mv = new MultiValue(name);

                this._specConc.Add(mv);


            }



        }





    }
}
